/*
 *  Copyright (C) 2010 MADSA.
 *
 *  This program is free software: you can redistribute it and/or modify
 *  it under the terms of the GNU General Public License as published by
 *  the Free Software Foundation, either version 3 of the License, or
 *  (at your option) any later version.
 *
 *  This program is distributed in the hope that it will be useful,
 *  but WITHOUT ANY WARRANTY; without even the implied warranty of
 *  MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
 *  GNU General Public License for more details.
 *
 *  You should have received a copy of the GNU General Public License
 *  along with this program.  If not, see http://www.gnu.org/licenses/. 
 *
 *  Author:  Jorge Pintado de Santiago
 *          
 */

package com.madsa.maps;

import java.io.IOException;
import java.net.HttpURLConnection;
import java.net.MalformedURLException;
import java.net.URL;

import javax.xml.parsers.DocumentBuilder;
import javax.xml.parsers.DocumentBuilderFactory;
import javax.xml.parsers.ParserConfigurationException;

import org.w3c.dom.Document;
import org.xml.sax.SAXException;

import com.google.android.maps.GeoPoint;
import com.google.android.maps.MapActivity;
import com.google.android.maps.MapController;
import com.google.android.maps.MapView;
import com.sisof.R;

import android.content.Context;
import android.graphics.Color;
import android.location.Address;
import android.location.Criteria;
import android.location.Geocoder;
import android.location.Location;
import android.location.LocationListener;
import android.location.LocationManager;
import android.os.Bundle;
import android.util.Log;
import android.view.Menu;
import android.view.MenuItem;
import android.widget.TextView;

public class MapsManualRoute extends MapActivity {
	
    private static final int SATELLITE_VIEW = Menu.FIRST;
    private static final int MAP_VIEW = Menu.FIRST+1;

    MyPositionOverlay positionOverlay;
	MapController mapController;
	private MapView myMapView;
	private String destineDirection="";
	double src_lat; // the testing source
	double src_long;
	double dest_lat; // the testing destination
	double dest_long;
		
	@Override
	protected boolean isRouteDisplayed() {
	  return false;
	}

	@Override
	public void onCreate(Bundle savedInstanceState) {
	super.onCreate(savedInstanceState);
	setContentView(R.layout.maps);
	
	myMapView = (MapView)findViewById(R.id.myMapView);
	// Get the Map View’s controller
	mapController = myMapView.getController();
	// Configure the map display options
	myMapView.setSatellite(false);
	myMapView.displayZoomControls(false);
	// Zoom in
	mapController.setZoom(17);
	//set enabled zoom controls
	myMapView.setBuiltInZoomControls(true);

	
	Bundle extras  = getIntent().getExtras(); 
	if(extras != null){ 
		String destine = extras.getString("destino");
		destineDirection = destine.split(";")[1];
	}else{
		destineDirection = null;
	}

	LocationManager locationManager;
	String context = Context.LOCATION_SERVICE;
	locationManager = (LocationManager)getSystemService(context);
	
	Criteria criteria = new Criteria();
	criteria.setAccuracy(Criteria.ACCURACY_FINE);
	criteria.setAltitudeRequired(false);
	criteria.setBearingRequired(false);
	criteria.setCostAllowed(true);
	criteria.setPowerRequirement(Criteria.POWER_LOW);
	String provider = locationManager.getBestProvider(criteria, true);
	
	Location location = locationManager.getLastKnownLocation(provider);
	updateWithNewLocation(location);
	
	locationManager.requestLocationUpdates(provider, 10000, 10,
			locationListener);
		
	Geocoder fwdGeocoder = new Geocoder(this);
	try{
		Address destineLocation = fwdGeocoder.getFromLocationName(destineDirection, 1).get(0);
		dest_lat = destineLocation.getLatitude();
		dest_long = destineLocation.getLongitude();
	}catch (IOException e) {}
		
	GeoPoint srcGeoPoint = new GeoPoint((int) (src_lat * 1E6),
	(int) (src_long * 1E6));
	GeoPoint destGeoPoint = new GeoPoint((int) (dest_lat * 1E6),
	(int) (dest_long * 1E6));

	DrawPath(srcGeoPoint, destGeoPoint, Color.GREEN, myMapView);

	myMapView.getController().animateTo(srcGeoPoint);
	myMapView.getController().setZoom(15);

	}
		
	private void DrawPath(GeoPoint src,GeoPoint dest, int color, MapView mMapView01){
		// connect to map web service
		StringBuilder urlString = new StringBuilder();
		urlString.append("http://maps.google.com/maps?f=d&hl=en");
		urlString.append("&saddr=");//from
		urlString.append( Double.toString((double)src.getLatitudeE6()/1.0E6 ));
		urlString.append(",");
		urlString.append( Double.toString((double)src.getLongitudeE6()/1.0E6 ));
		urlString.append("&daddr=");//to
		urlString.append( Double.toString((double)dest.getLatitudeE6()/1.0E6 ));
		urlString.append(",");
		urlString.append( Double.toString((double)dest.getLongitudeE6()/1.0E6 ));
		urlString.append("&ie=UTF8&0&om=0&output=kml");
		Log.d("xxx","URL="+urlString.toString());
		// get the kml (XML) doc. And parse it to get the coordinates(direction route).
		Document doc = null;
		HttpURLConnection urlConnection= null;
		URL url = null;
		try{
			url = new URL(urlString.toString());
			urlConnection=(HttpURLConnection)url.openConnection();
			urlConnection.setRequestMethod("GET");
			urlConnection.setDoOutput(true);
			urlConnection.setDoInput(true);
			urlConnection.connect();

			DocumentBuilderFactory dbf = DocumentBuilderFactory.newInstance();
			DocumentBuilder db = dbf.newDocumentBuilder();
			doc = db.parse(urlConnection.getInputStream());

			if(doc.getElementsByTagName("GeometryCollection").getLength()>0){
				//String path = doc.getElementsByTagName("GeometryCollection").item(0).getFirstChild().getFirstChild().getNodeName();
				String path = doc.getElementsByTagName("GeometryCollection").item(0).getFirstChild().getFirstChild().getFirstChild().getNodeValue() ;
				Log.d("xxx","path="+ path);
				String [] pairs = path.split(" ");
				String[] lngLat = pairs[0].split(","); // lngLat[0]=longitude lngLat[1]=latitude lngLat[2]=height
				// src
				GeoPoint startGP = new GeoPoint((int)(Double.parseDouble(lngLat[1])*1E6),(int)(Double.parseDouble(lngLat[0])*1E6));
				mMapView01.getOverlays().add(new MyOverlay(startGP,startGP,1));
				GeoPoint gp1;
				GeoPoint gp2 = startGP;
				for(int i=1;i<pairs.length;i++){ // the last one would be crash
					lngLat = pairs[i].split(",");
					gp1 = gp2;
					// watch out! For GeoPoint, first:latitude, second:longitude
					gp2 = new GeoPoint((int)(Double.parseDouble(lngLat[1])*1E6),(int)(Double.parseDouble(lngLat[0])*1E6));
					mMapView01.getOverlays().add(new MyOverlay(gp1,gp2,2,color));
					Log.d("xxx","pair:" + pairs[i]);
				}
				mMapView01.getOverlays().add(new MyOverlay(dest,dest, 3)); // use the default color
			}
		}
		catch (MalformedURLException e){
			e.printStackTrace();
		}
		catch (IOException e) {
			e.printStackTrace();
		}
		catch (ParserConfigurationException e){
			e.printStackTrace();
		}
		catch (SAXException e){
			e.printStackTrace();
		}
	}
	
	private void updateWithNewLocation(Location location) {
		TextView destineText;
		destineText = (TextView)findViewById(R.id.myLocationText);

		if (location != null) {		 

			src_lat = location.getLatitude();
			src_long = location.getLongitude();
			
			// Update the map location.
			Double geoLat = location.getLatitude()*1E6;
			Double geoLng = location.getLongitude()*1E6;
			GeoPoint point = new GeoPoint(geoLat.intValue(),
		                                geoLng.intValue());
			mapController.animateTo(point);

			GeoPoint srcGeoPoint = new GeoPoint((int) (src_lat * 1E6),
					(int) (src_long * 1E6));
			GeoPoint destGeoPoint = new GeoPoint((int) (dest_lat * 1E6),
					(int) (dest_long * 1E6));

			DrawPath(srcGeoPoint, destGeoPoint, Color.GREEN, myMapView);

		} 
			destineText.setText("Destino: " + destineDirection);
			
	}

	private final LocationListener locationListener = new LocationListener() {
		public void onLocationChanged(Location location) {
			updateWithNewLocation(location);
		}
		public void onProviderDisabled(String provider){
			updateWithNewLocation(null);
		}
		public void onProviderEnabled(String provider){ }
		public void onStatusChanged(String provider, int status,
								Bundle extras){ }
		};

		@Override
		public boolean onCreateOptionsMenu(Menu menu) {
			super.onCreateOptionsMenu(menu);
			menu.add(Menu.NONE, SATELLITE_VIEW, 0, R.string.m_satellite_view);
			menu.add(Menu.NONE, MAP_VIEW, 0, R.string.m_map_view);
			return true;
		}
    
		public boolean onMenuItemSelected(int featureId, MenuItem item) {
			super.onMenuItemSelected(featureId, item);
              	switch(item.getItemId()) {
              	case SATELLITE_VIEW:
              		myMapView.setSatellite(true);
              		break;
              	case MAP_VIEW:
              		myMapView.setSatellite(false);
              		break;
              	}
              	return true;
		}


}